package org.ascollada.core
{
	public class DaeTransform extends DaeElement
	{
		public var type :String;
		public var data :Array;
		
		public function DaeTransform(document:DaeDocument, element:XML=null)
		{
			super(document, element);
		}
		
		public override function destroy():void
		{
			super.destroy();
			this.type = null;
			this.data = null;
		}
		
		public override function read(element:XML):void
		{
			super.read(element);
			
			this.type = element.name().localName;
			this.data = readStringArray(element);
			
			if(this.data && this.data.length && this.data[0].indexOf(",") != -1)
			{
				for(var i:int = 0; i < this.data.length; i++)
				{
					this.data[i] = this.data[i].replace(/,/, ".");
				}
			}
		}
		
		/**
		 * 
		 */ 
		public function toMatrix():Array
		{
			var toRadians :Number = Math.PI/180;
			var m :Array = this.data;
			
			switch(this.type)
			{
				case "matrix":
					return m;
				case "rotate":
					return buildRotation(m[0], m[1], m[2], m[3]*toRadians);	
				case "scale":
					return buildScale(m[0], m[1], m[2]);	
				case "translate":
					return buildTranslation(m[0], m[1], m[2]);	
				default:
					break;
			}	
			
			return null;	
		}
		
		private function buildRotation(x:Number, y:Number, z:Number, rad:Number):Array
		{
			var m :Array = new Array(16);
			
			var nCos:Number	= Math.cos( rad );
			var nSin:Number	= Math.sin( rad );
			var scos:Number	= 1 - nCos;
	
			var sxy	:Number = x * y * scos;
			var syz	:Number = y * z * scos;
			var sxz	:Number = x * z * scos;
			var sz	:Number = nSin * z;
			var sy	:Number = nSin * y;
			var sx	:Number = nSin * x;
	
			m[0] =  nCos + x * x * scos;
			m[1] = -sz   + sxy;
			m[2] =  sy   + sxz;
			m[3] = 0;
			
			m[4] =  sz   + sxy;
			m[5] =  nCos + y * y * scos;
			m[6] = -sx   + syz;
			m[7] = 0;
			
			m[8] = -sy   + sxz;
			m[9] =  sx   + syz;
			m[10] =  nCos + z * z * scos;
			m[11] = 0;
			
			m[12] = 0;
			m[13] = 0;
			m[14] = 0;
			m[15] = 1;
			
			return m;
		}
		
		private function buildScale(x:Number, y:Number, z:Number):Array
		{
			var m :Array = [
				x, 0, 0, 0,
				0, y, 0, 0,
				0, 0, z, 0,
				0, 0, 0, 1
			];
			return m;
		}
		
		private function buildTranslation(x:Number, y:Number, z:Number):Array
		{
			var m :Array = [
				1, 0, 0, x,
				0, 1, 0, y,
				0, 0, 1, z,
				0, 0, 0, 1
			];
			return m;
		}
	}
}